#pragma once

// -----------------------------------------------------------------------------

#include "Win32.String.h"
#include "Win32.Diagnostics.Result.h"
#include "Win32.Data.DataSource.h"
#include "Win32.DateTime.h"
#include "Win32.Data.Odbc.h"

namespace Kif
{
namespace Win32
{
namespace DataObjects
{

enum ImageFormat
{
   MediaFormat_Unknown    = 0,
   MediaFormat_Jpeg       = 1,
   MediaFormat_Mpeg       = 2,
   MediaFormat_TextFile   = 3,
   MediaFormat_RtfFile    = 4,
   MediaFormat_MsWordFile = 5,
   MediaFormat_PdfFile    = 6,
   MediaFormat_Jpeg2000   = 20,
   MediaFormat_Wsq        = 21,
   MediaFormat_Bitmap     = 22,
   MediaFormat_VectorData = 23,
   MediaFormat_FaxGroup4  = 24
}  ;  // end of ImageFormat

enum SubmissionType
{
   SubmissionType_Unknown = 0,
   SubmissionType_EdiX12  = 1,
   SubmissionType_NIST    = 100
}  ;  // end of SubmissionType

enum SubmissionKeyType
{
   SubmissionKeyId_Unknown   = 0,
   SubmissionKeyId_OffenseNo = 1
}  ;  // end of SubmissionKeyType

enum SubmissionContentType
{
   SubmissionContentType_Unknown = 0,
   SubmissionContentType_CriminalTenPrintSubmissionWithAnswer = 1,  // CAR
   SubmissionContentType_CriminalTenPrintSubmissionNoAnswered = 2,  // CAN
   SubmissionContentType_FederalApplicantNoCharge = 3,              // FANC
   SubmissionContentType_FederalApplicantUserFee = 4,               // FAUF
   SubmissionContentType_NonFederalApplicantUserFee = 5,            // NFUF
   SubmissionContentType_MiscellaneousApplicant = 6,                // MAP
   SubmissionContentType_KnownDeceased = 7,                         // DEK
   SubmissionContentType_UnknownDeceased = 8,                       // DEU
   SubmissionContentType_MissingPerson = 9,                         // MPR
   SubmissionContentType_AmnesiaVictim = 10,                        // AMN
   SubmissionContentType_SubmissionResults = 11,                    // SRE
   SubmissionContentType_TenPrintTransactionErrors = 12,            // ERRT
   SubmissionContentType_AdministrativeTransactionErrors = 13,      // ERRA
   SubmissionContentType_LatentTransactionErrors = 14,              // ERRL
   SubmissionContentType_NonfederalAdvancedPayment = 15             // NFAP
}  ;  // end of SubmissionContentType

enum SubmissionStatus
{
   SubmissionStatus_Unknown    = 0,
   SubmissionStatus_Registered = 1,
   SubmissionStatus_Parsed     = 2,
   SubmissionStatus_Accepted   = 10,
   SubmissionStatus_Rejected   = 11
}  ;  // end of SubmissionStatus

enum SubmissionMessageType
{
   MessageType_Ignore        = -1,
   MessageType_Unknown       = 0,
   MessageType_ErrorMessages = 1,
   MessageType_DemographicDetails = 100,
   MessageType_SubmissionContent = 101
}  ;  // end of SubmissionMessageType

enum MediaType
{
   MediaType_Unknown               = 0,
   MediaType_RightThumb            = 101,
   MediaType_RightIndexFinger      = 102,
   MediaType_RightMiddleFinger     = 103,
   MediaType_RightRingFinger       = 104,
   MediaType_RightLittleFinger     = 105,
   MediaType_LeftThumb             = 106,
   MediaType_LeftIndexFinger       = 107,
   MediaType_LeftMiddleFinger      = 108,
   MediaType_LeftRingFinger        = 109,
   MediaType_LeftLittleFinger      = 110,
   MediaType_PlainRightThumb       = 111,
   MediaType_PlainLeftThumb        = 112,
   MediaType_PlainRightFourFingers = 113,
   MediaType_PlainLeftFourFingers  = 114,
   MediaType_LeftAndRightThumbs    = 115,
   MediaType_FullFaceFrontal       = 116,
   MediaType_RightProfile          = 117,
   MediaType_LeftProfile           = 118,
   MediaType_AnglePose             = 119,
   MediaType_UnknownPalm           = 120,
   MediaType_RightFullPalm         = 121,
   MediaType_RightWritersPalm      = 122,
   MediaType_LeftFullPalm          = 123,
   MediaType_LeftWritersPalm       = 124,
   MediaType_RightLowerPalm        = 125,
   MediaType_RightUpperPalm        = 126,
   MediaType_LeftLowerPalm         = 127,
   MediaType_LeftUpperPalm         = 128,
   MediaType_RightOtherPalm        = 129,
   MediaType_LeftOtherPalm         = 130,

   MediaType_PalmPrintLeftHand     = 131,
   MediaType_OutsideEdgeLeftHand   = 132,
   MediaType_InsideEdgeLeftHand    = 133,
   MediaType_WristLeftHand         = 134,
   MediaType_PalmPrintRightHand    = 135,
   MediaType_OutsideEdgeRightHand  = 136,
   MediaType_InsideEdgeRightHand   = 137,
   MediaType_WristRightHand        = 138,
   MediaType_SoleLeftFoot          = 139,
   MediaType_ToesLeftFoot          = 140,
   MediaType_SoleRightFoot         = 141,
   MediaType_ToesRightFoot         = 142,
   MediaType_Part1OfTenPrintForm   = 143,
   MediaType_Part2OfTenPrintForm   = 144,
   MediaType_Part3OfTenPrintForm   = 145,
   MediaType_Part4OfTenPrintForm   = 146,
   MediaType_Part5OfTenPrintForm   = 147,
   MediaType_Part6OfTenPrintForm   = 148,
   MediaType_CompleteTenPrintForm  = 149,
   MediaType_OtherNistImage        = 150,

   MediaType_FingertipRightThumb        = 151,
   MediaType_FingertipRightIndexFinger  = 152,
   MediaType_FingertipRightMiddleFinger = 153,
   MediaType_FingertipRightRingFinger   = 154,
   MediaType_FingertipRightLittleFinger = 155,

   MediaType_FingertipLeftThumb         = 156,
   MediaType_FingertipLeftIndexFinger   = 157,
   MediaType_FingertipLeftMiddleFinger  = 158,
   MediaType_FingertipLeftRingFinger    = 159,
   MediaType_FingertipLeftLittleFinger  = 160,

   MediaType_SignatureOfSubject    = 200,
   MediaType_SignatureOfOfficer    = 201,

   MediaType_Tattoo                = 901
}  ;  // end of MediaType

enum SubmissionError
{
   SubmissionError_Success = 0,
   SubmissionError_InvalidSubmissionId = -1,
   SubmissionError_FailedToRegisterSubmission = -2,
   SubmissionError_SubmissionRegistryAlreadyExists = -3,
   SubmissionError_FailedToUpdateSubmssionStatus   = -4,
   SubmissionError_FailedToInsertStatusAndMessage  = -5,
   SubmissionError_SubmissionNotFound    = -6,
   SubmissionError_FailedToRegisterMedia = -7,
   SubmissionError_BadFileFormatUnreadable = -8,
   SubmissionError_NotEnoughSpaceForPSID = -9,
   SubmissionError_FailedReplacingPSIDFile = -10,
   SubmissionError_PSIDNotFound = -11,
   SubmissionError_IncidentIdNotFound = -12,
   SubmissionError_PSIDNotRelatedToIncidentId = -13,
   SubmissionError_NoneOneOrManyReferencesFound = -14,
   SubmissionError_FailedToValidateSubmission = -15,
   SubmissionError_FailedReadingFile = -16,
   SubmissionError_FailedToInsertKeyId = -17,
   SubmissionError_FailedReplacingFileNotEnoughSpace = -18,
   SubmissionError_TagToReplaceNotFound = -19,
   SubmissionError_FailedRetrievingSubmissionId = -20,
   SubmissionError_InvalidIncidentId = -93,
   SubmissionError_DatabaseRequestFailed = -99
}  ;  // end of SubmissionError

class SubmissionDbConnection
{
public:

   Kif::Win32::Diagnostics::Result LastResult;
   Kif::Win32::Data::OdbcClient::OdbcConnection Connection;
   bool Connected;

   bool Connect(Kif::Win32::Data::DataSourceInfo &dataSource);
   inline void Disconnect()
   {
      if (Connected)
         Connection.Disconnect();
      Connected = false;
   }  // end of Disconnect

   SubmissionDbConnection()
   {
      LastResult.Clear();
      Connected = false;
   }
  ~SubmissionDbConnection()
   {
      Disconnect();
   }

}  ;  // end of SubmissionDbConnection

class Submission
{
private:
public:

   static const int SubmissionIdLength = 20;

   static Kif::Win32::String *GetEntrySubmissionStatusMessage(short statusNo);

   static bool GetErrorMessage(long errorNo, TCHAR *location,
      Kif::Win32::Diagnostics::Result &result);
   static TCHAR *GetErrorMessage(long errorNo);

   static Kif::Win32::Diagnostics::Result *GetSessionId(
      SubmissionDbConnection &connection,
      Kif::Win32::String &outSessionId);

   static Kif::Win32::Diagnostics::Result *GetSubmissionId(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &trackingId,
      Kif::Win32::String &outSubmissionId);

   static Kif::Win32::Diagnostics::Result *RegisterSubmission(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &trackingId,
      Kif::Win32::String &referenceId,
      Kif::Win32::String &controlId,
      Kif::Win32::String &controlReferenceId,
      Kif::Win32::String &sourceId,
      Kif::Win32::String &destinationId,
      Kif::Win32::DateTime *submissionDate,
      Kif::Win32::String &submittedFileName,
      DWORD sizeInBytes,
      short typeNo,
      short contentTypeNo,
      BYTE *binaryData,
      DWORD binaryDataSizeInBytes,
      Kif::Win32::String &outSubmissionId,
      TCHAR searchResultsFindings);

   static Kif::Win32::Diagnostics::Result *RegisterMedia(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &submissionId,
      Kif::Win32::String &mediaId,
      short formatNo,
      short typeNo,
      TCHAR *submitterId,
      Kif::Win32::DateTime *captureDate,
      Kif::Win32::String &metaData,
      BYTE *binaryData,
      DWORD binaryDataSizeInBytes);

   static Kif::Win32::Diagnostics::
      ResultObject<Kif::Win32::MemoryBuffer<BYTE>> *SubmissionGetFileData(
         SubmissionDbConnection &dbConnection,
         Kif::Win32::String &sessionId,
         Kif::Win32::String &submissionId,
         Kif::Win32::String &transactionControlNumber);

   static Kif::Win32::Diagnostics::Result *RegisterKeyId(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &submissionId,
      Kif::Win32::DataObjects::SubmissionKeyType keyType,
      TCHAR *keyId);

   static Kif::Win32::Diagnostics::Result *SubmissionValidateEntry(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &submissionId,
      Kif::Win32::String &referenceId,
      short *statusNo);

   static Kif::Win32::Diagnostics::Result *UpdateSubmissionStatus(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &submissionId,
      short statusNo,
      short messageTypeNo,
      Kif::Win32::String &xmlMessages);

   static Kif::Win32::Diagnostics::Result *RegisterMessage(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &submissionId,
      short messageTypeNo,
      Kif::Win32::String &xmlMessages)
   {
      return(UpdateSubmissionStatus(
         connection, sessionId, submissionId, 1, messageTypeNo, xmlMessages));
   }

   static Kif::Win32::Diagnostics::Result *SubmissionQueueUpdate(
      SubmissionDbConnection &connection,
      Kif::Win32::String &sessionId,
      Kif::Win32::String &submissionId,
      Kif::Win32::String &referenceId1,
      Kif::Win32::String &referenceId2,
      Kif::Win32::String &referenceId3,
      short statusNo,
      short optionNo,
      Kif::Win32::String &outReferenceId);

}  ;  // end of Submission class

}  // end of Kif::Win32::DataObjects
}  // end of Kif::Win32
}  // end of Kif

